package com.tywj.panda.home.buy

import android.os.Bundle
import androidx.lifecycle.Observer
import com.alibaba.android.arouter.facade.annotation.Route
import com.bigkoo.pickerview.builder.OptionsPickerBuilder
import com.bigkoo.pickerview.listener.OnOptionsSelectListener
import com.bigkoo.pickerview.view.OptionsPickerView
import com.tywj.lib.core.common.extension.gone
import com.tywj.lib.core.common.extension.onClick
import com.tywj.lib.core.common.extension.visible
import com.tywj.lib.core.common.util.ResourcesUtil
import com.tywj.lib.route.RouteParam
import com.tywj.lib.route.RouteUtil
import com.tywj.navigation.tool.MapTool
import com.tywj.panda.customer.common.dialog.BuyDialog
import com.tywj.panda.customer.common.entity.CalendarPriceEntity
import com.tywj.panda.customer.common.entity.HomeLineDetailsEntity
import com.tywj.panda.customer.common.entity.SelectedPriceDateEntity
import com.tywj.panda.customer.common.event.PriceEvent
import com.tywj.panda.customer.common.http.PDArrayCallback
import com.tywj.panda.customer.common.http.PDObjectCallback
import com.tywj.panda.customer.common.provider.IPayService
import com.tywj.panda.customer.common.provider.IUserService
import com.tywj.panda.customer.common.tool.MoneyTool
import com.tywj.panda.customer.common.tool.TimeTool
import com.tywj.panda.customer.common.view.base.MyBaseActivity
import com.tywj.panda.customer.common.widget.calendar.CalendarView
import com.tywj.panda.home.R
import com.tywj.panda.home.api.HomeApi
import com.tywj.panda.home.entity.HomeLineTimeEntity
import com.tywj.panda.home.entity.OrderEntity
import com.tywj.panda.home.event.HomeEvent
import com.tywj.panda.home.route.HomeRoute
import kotlinx.android.synthetic.main.home_activity_buy_tickets.*


/**
 * <pre>
 *     author : June Yang
 *     time   : 2020/05/22
 *     desc   : 购买票界面
 *     version: 1.0.0
 * </pre>
 */
@Route(path = HomeRoute.HOME_BUY)
class HomeBuyTicketsActivity : MyBaseActivity() {

    companion object {
        //是否从首页到购买页
        const val PARAMS_IS_FROM_HOME = "is_from_home"
        const val PARAMS_LINE_CODE = "lineCode"
        const val PARAMS_LINE_NAME = "lineName"
        const val PARAMS_START_POS = "startPos"
        const val PARAMS_END_POS = "endPos"
        const val PARAMS_STATIONS_LIST = "stationList"

        //选择的时间列表位置
        const val PARAMS_TIME_INDEX = "timeIndex"

        const val DEFAULT_POS = -1
    }

    //站点的位置 、记录当前选择的起点位置
    private var mStartPosition = DEFAULT_POS
    private var mEndPosition = DEFAULT_POS

    //站点的名称
    private var mStartStation = ""
    private var mEndStation = ""

    //班次时刻表位置
    private var mTimeSelectedIndex = 0

    //所有站点信息
    private var stationsList = ArrayList<HomeLineDetailsEntity.Station>()

    override fun getLayoutID(): Int = R.layout.home_activity_buy_tickets

    // 预约时间数据
    private val timeList = ArrayList<String>()

    // 预约地址数据
    private val addressList = ArrayList<String>()

    private val addressEndList = ArrayList<String>()

    // 预约地址选择器(起点)
    private lateinit var startAddressPickerView: OptionsPickerView<String>

    //预约地址选择器(终点)
    private lateinit var endAddressPickerView: OptionsPickerView<String>

    //预约时间选择器
    private lateinit var appointmentTimePickerView: OptionsPickerView<String>


    //乘车人数
    private var num = 1

    //选择日期总价
    private var totalPrice = 0

    //支付总价
    private var payFee = 0

    private var orderNo = ""

    private var isFromHome = false


    private var lineCode = ""

    //发车时间
    private var defaultLineTime = ""

    //线路名称
    private var lineName = ""

    //当前第几页
    private var currentPosition = 0

    //已选择的商品列表
    private var selectedPriceDateList = ArrayList<SelectedPriceDateEntity>()

    private val buyDialog by lazy { initBuyDialog() }

    override fun initVariable(savedInstanceState: Bundle?) {
        super.initVariable(savedInstanceState)

        val routeParam = RouteParam(this)
        lineCode = routeParam.getString(PARAMS_LINE_CODE)
        lineName = routeParam.getString(PARAMS_LINE_NAME)

        isFromHome = routeParam.getBoolean(PARAMS_IS_FROM_HOME)

        if (isFromHome) {
            //如果从首页

        } else {
            mStartPosition = routeParam.getInt(PARAMS_START_POS)
            mEndPosition = routeParam.getInt(PARAMS_END_POS)
            stationsList = routeParam.getParcelableArrayList(PARAMS_STATIONS_LIST)!!

            mTimeSelectedIndex = routeParam.getInt(PARAMS_TIME_INDEX)


            if (mStartPosition == DEFAULT_POS) {
                mStartPosition = 0
            }

            if (mEndPosition == DEFAULT_POS) {
                mEndPosition = stationsList.lastIndex
            }
            //从首页中到购买页 获取详再次获取线路数据
            if (stationsList.isNotEmpty()) {

                mStartStation = stationsList[mStartPosition].name
                mEndStation = stationsList[mEndPosition].name

                etStartPoint.setText(mStartStation)
                etEndPoint.setText(mEndStation)


                tvStartTimePlan.text = String.format(
                    ResourcesUtil.getString(R.string.home_plan_time),
                    stationsList[mStartPosition].timeAdd
                )
                tvEndTimePlan.text =
                    String.format(ResourcesUtil.getString(R.string.home_plan_time), stationsList[mEndPosition].timeAdd)
            }

            stationsList.forEach {
                addressList.add(it.name)
            }
        }
    }

    override fun initView(savedInstanceState: Bundle?) {
        super.initView(savedInstanceState)
        initAddressPickerView()
        initTimePickerView()
    }

    override fun initListener() {
        super.initListener()

        titleLayout.getRightTextView().onClick {
            buyDialog.showDialog(supportFragmentManager)
        }

        //选择上车点
        etStartPoint.onClick {
            startAddressPickerView.show()
        }
        //选择下车点
        etEndPoint.onClick {

            if (etStartPoint.text.toString().isEmpty()) {
                shortToast("请先选择上车点")
                return@onClick
            }
            //重新拼接已选择上车点之后的下车地址列表
            clearEndStation()
            endAddressPickerView.show()
        }

        flStartTime.onClick {
            appointmentTimePickerView.show()
        }
        //去购买
        btnBuy.onClick {
            if (etStartPoint.text.toString().isEmpty()) {
                shortToast("请选择上车地点")
                return@onClick
            }

            if (etEndPoint.text.toString().isEmpty()) {
                shortToast("请选择下车地点")
                return@onClick
            }

            if (selectedPriceDateList.isEmpty()) {
                shortToast(R.string.home_please_selected_date)
                return@onClick
            }

            //判断是否起点和终点位置合理
            if (mStartPosition >= mEndPosition) {
                shortToast("上车站点应该在下车点之前，请重新选择")
                return@onClick
            }
            //生成订单号
            toPrePay()
        }


        ibPlus.onClick {
            if (num == 1) {
                shortToast("最小人数为1")
                return@onClick
            }
            num--
            tvNum.text = num.toString()
            payFee = totalPrice * num
            tvPrice.text = MoneyTool.formatFen(payFee)

        }
        ibAdd.onClick {
            num++
            tvNum.text = num.toString()

            payFee = totalPrice * num
            tvPrice.text = MoneyTool.formatFen(payFee)
        }


        statusLayout.setOnErrorLayoutButtonClick {
            loadDataLineDetails(isFromHome)
        }

        statusLayout.setOnEmptyLayoutButtonClick {
            loadDataLineDetails(isFromHome)
        }

        //本页全选
        cbCheckedCurrentPage.setOnCheckedChangeListener { _, isChecked ->
            if (isChecked) {
                //判断当前页和当前页的数据范
                shortToast("全选")
            } else {
                shortToast("取消全选")
            }
        }

        //监听当前第几页
        datePrice.selectedCurrentAll(object : CalendarView.ISelectedAll {
            override fun selectedCurrent(position: Int) {
                currentPosition = position

//                shortToast("当前第" + currentPosition + "页")
            }
        })

        //同步显示的价格 注意目前是分页的位置处理 需要将几个月的数据合并到一起
        PriceEvent.getSelectedPriceList.observe(this, Observer { hashMap ->
            handleSelectedPrice(hashMap)
        })
    }


    override fun loadDataOnCreate() {
        super.loadDataOnCreate()

        loadDataLineDetails(isFromHome)
    }

    //1.从首页进来需要再次请求线路获取站点
    private fun loadDataLineDetails(isFromHome: Boolean) {
        statusLayout.showLoadingLayout()
        if (isFromHome) {
            HomeApi.getCRMLineDetails(lineCode).attachToLifecycle(this)
                .execute(object : PDObjectCallback<HomeLineDetailsEntity>(
                    HomeLineDetailsEntity::class.java
                ) {
                    override fun success(data: HomeLineDetailsEntity) {
                        statusLayout.showContentLayout()
                        //得到站点信息
                        mStartStation = data.start.name
                        mEndStation = data.end.name

                        lineName = data.name

                        etStartPoint.setText(mStartStation)
                        etEndPoint.setText(mEndStation)

                        //拼接站点列表
                        stationsList.clear()
                        stationsList.add(data.start)
                        stationsList.addAll(data.ways)
                        stationsList.add(data.end)


                        stationsList.forEach {
                            addressList.add(it.name)
                        }
                        loadDataTime()
                    }

                    override fun error(code: Int, message: String) {
                        super.error(code, message)
                        statusLayout.showErrorLayoutByCode(code, message)
                    }
                })
        } else {
            //2.从详情页进来后直接，开始加载日历时间段 和票价
            loadDataTime()
        }
    }


    private fun loadDataTime() {
        statusLayout.showLoadingLayout()
        HomeApi.getLineTimeByDate(lineCode).attachToLifecycle(this)
            .execute(object : PDArrayCallback<HomeLineTimeEntity>(HomeLineTimeEntity::class.java) {
                override fun success(data: ArrayList<HomeLineTimeEntity>) {
                    statusLayout.showContentLayout()
                    handleData(data)
                }

                override fun error(code: Int, message: String) {
                    super.error(code, message)
                    statusLayout.showErrorLayoutByCode(code, message)
                    gone(flGotoPay)
                }
            })
    }

    private fun handleData(data: ArrayList<HomeLineTimeEntity>) {

        if (data.isEmpty()) {
            statusLayout.showEmptyLayout()
            return
        } else {
            statusLayout.showContentLayout()
            visible(flGotoPay)
        }

        timeList.clear()

        data.forEach {
            timeList.add(it.lineTime)
        }
        defaultLineTime = timeList[mTimeSelectedIndex]
        //更新出发时间
        tvStartTime.text = defaultLineTime

        //同时处理时间点：
        refreshBusTimeList()

        getDatePriceByTime(defaultLineTime)
    }

    //为同步显示时间和地点
    private fun initAddressPickerView() {

        val startAddressOptions = OptionsPickerBuilder(this, OnOptionsSelectListener { options1, _, _, _ ->

            if (options1 == stationsList.lastIndex) {
                shortToast("当前站点不能设置为终点")
                return@OnOptionsSelectListener
            }

            val address = addressList[options1]

            mStartPosition = options1

            mStartStation = address

            etStartPoint.setText(mStartStation)

            tvStartTimePlan.text =
                String.format(
                    ResourcesUtil.getString(R.string.home_plan_time),
                    stationsList[mStartPosition].timeAdd
                )

            //选择好起点后，重新拼接终点地址
            if (etEndPoint.text.toString().isNotEmpty()) {
                if (mStartPosition >= mEndPosition) {
                    etEndPoint.setText("")
                    tvEndTimePlan.text = ""
                }
            }

        }).setTitleColor(ResourcesUtil.getColor(com.tywj.navigation.R.color.common_black_33))
            .setTitleSize(20)
            .setCancelColor(ResourcesUtil.getColor(com.tywj.navigation.R.color.common_gray_B2))
            .setSubCalSize(16)
            .setSubmitColor(ResourcesUtil.getColor(com.tywj.navigation.R.color.common_yellow_FD))
            .setSubCalSize(16)
            .build<String>()
        startAddressOptions.setNPicker(addressList, null, null)
        startAddressOptions.setSelectOptions(0, 0, 0)
        startAddressPickerView = startAddressOptions


        val endAddressOptions = OptionsPickerBuilder(this, OnOptionsSelectListener { options1, _, _, _ ->

            val address = addressEndList[options1]
            //思路：根据名字去返查找名字所在的stationsList的位置和时间
            val index = findIndexByName(address)

            if (index != DEFAULT_POS) {
                mEndPosition = index
            } else {
                mEndPosition = stationsList.lastIndex
            }

            mEndStation = address
            etEndPoint.setText(mEndStation)
            tvEndTimePlan.text =
                String.format(ResourcesUtil.getString(R.string.home_plan_time), stationsList[mEndPosition].timeAdd)


        }).setTitleColor(ResourcesUtil.getColor(com.tywj.navigation.R.color.common_black_33))
            .setTitleSize(20)
            .setCancelColor(ResourcesUtil.getColor(com.tywj.navigation.R.color.common_gray_B2))
            .setSubCalSize(16)
            .setSubmitColor(ResourcesUtil.getColor(com.tywj.navigation.R.color.common_yellow_FD))
            .setSubCalSize(16)
            .build<String>()
        endAddressOptions.setNPicker(addressEndList, null, null)
        endAddressOptions.setSelectOptions(0, 0, 0)
        endAddressPickerView = endAddressOptions
    }

    //记录当前选择的日期位置，防止多次查询相同的数据
    private var mPreTimePosition = -1
    private fun initTimePickerView() {
        val timeOptions = OptionsPickerBuilder(this, OnOptionsSelectListener { options1, _, _, _ ->

            if (mPreTimePosition == options1) {
                return@OnOptionsSelectListener
            }

            mPreTimePosition = options1
            val time = timeList[options1]

            defaultLineTime = time
            tvStartTime.text = defaultLineTime

            getDatePriceByTime(defaultLineTime)

            refreshBusTimeList()


        }).setTitleColor(ResourcesUtil.getColor(com.tywj.navigation.R.color.common_black_33))
            .setTitleSize(20)
            .setCancelColor(ResourcesUtil.getColor(com.tywj.navigation.R.color.common_gray_B2))
            .setSubCalSize(16)
            .setSubmitColor(ResourcesUtil.getColor(com.tywj.navigation.R.color.common_yellow_FD))
            .setSubCalSize(16)
            .build<String>()
        timeOptions.setNPicker(timeList, null, null)
        timeOptions.setSelectOptions(0, 0, 0)
        appointmentTimePickerView = timeOptions
    }

    private fun initBuyDialog(): BuyDialog {
        //as？如果不兼容 会返回为null  ?:为空时会初始化
        return supportFragmentManager.findFragmentByTag(BuyDialog.TAG) as? BuyDialog
            ?: BuyDialog()
    }

    private fun getDatePriceByTime(time: String) {
        showLoadingDialog()
        HomeApi.getDatePriceByTime(lineCode, time).attachToLifecycle(this)
            .execute(object : PDArrayCallback<CalendarPriceEntity>(
                CalendarPriceEntity::class.java
            ) {
                override fun success(data: ArrayList<CalendarPriceEntity>) {
                    handleDatePrice(data)
                    dismissLoadingDialog()

                }

                override fun error(code: Int, message: String) {
                    super.error(code, message)
                    statusLayout.showErrorLayoutByCode(code, message)
                    dismissLoadingDialog()
                }
            })
    }

    private fun handleDatePrice(data: ArrayList<CalendarPriceEntity>) {
        datePrice.loadDatePrice(this, data)
        tvPrice.text = MoneyTool.formatFen(0)

        //选择的人数价格重置
        selectedPriceDateList.clear()
        totalPrice = 0
        num = 1
        tvNum.text = num.toString()
    }


    /**
     * 生成订单
    1.造成订单号
    2.获取订单详情 或传递相关参数到下一界面
    3.发起预付款功能
     */
    private fun toPrePay() {
        showLoadingDialog()
        HomeApi.createOrder(
            cityName = MapTool.CITY_DEFAULT,
            startStation = mStartStation,
            endStation = mEndStation,
            onTime = stationsList[mStartPosition].timeAdd,
            offTime = stationsList[mEndPosition].timeAdd,
            LineCode = lineCode,
            lineTime = defaultLineTime,
            lineName = lineName,
            goodsList = selectedPriceDateList,
            number = num,
            money = payFee
        ).attachToLifecycle(this)
            .execute(object : PDObjectCallback<OrderEntity>(OrderEntity::class.java, true) {
                override fun success(data: OrderEntity) {
                    dismissLoadingDialog()
                    orderNo = data.orderNo
                    toPay(orderNo)
                }

                override fun error(code: Int, message: String) {
                    super.error(code, message)
                    dismissLoadingDialog()
                    shortToast(message)
                }
            })
    }

    //跳转到支付界面
    private fun toPay(orderNo: String) {
        //处理当前支付后的逻辑（可选）
        RouteUtil.getServiceProvider(IPayService::class.java)
            ?.toPay(orderNo, payFee, object : IPayService.Callback {
                override fun onPayResult(clickType: Int) {
                    handlePayResult(
                        orderNo, clickType
                    )
                }
            })?.navigation(this@HomeBuyTicketsActivity)
    }

    private fun handlePayResult(orderNo: String, clickType: Int) {
        when (clickType) {
            IPayService.CLICK_PAY_SUCCESS_DETAIL -> {
                //到详情页
                RouteUtil.getServiceProvider(IUserService::class.java)?.toDetails(orderNo)?.navigation(this)
                if (!isFromHome) {
                    HomeEvent.colseHomeServiceEvent.post(Unit)
                }
                finish()
            }
            IPayService.CLICK_PAY_SUCCESS_CLOSE -> {
                if (!isFromHome) {
                    HomeEvent.colseHomeServiceEvent.post(Unit)
                }
                finish()
            }
            IPayService.CLICK_PAY_FAIL_CLOSE -> {
                if (!isFromHome) {
                    HomeEvent.colseHomeServiceEvent.post(Unit)
                }
                finish()
            }
            IPayService.CLICK_CHOOSE_PAY_CLOSE -> {
                if (!isFromHome) {
                    HomeEvent.colseHomeServiceEvent.post(Unit)
                }
                finish()
            }
            else -> {
                finish()
            }
        }
    }

    //用户选择日期后同步显示
    private fun handleSelectedPrice(hashMap: HashMap<Int, ArrayList<CalendarPriceEntity>>) {
        val selectedPriceList = ArrayList<CalendarPriceEntity>()
        selectedPriceList.clear()
        selectedPriceDateList.clear()

        totalPrice = 0

        for ((key, value) in hashMap) {
//            LogUtil.d("当前第" + (key + 1) + "页" + "选择了" + value.size + "个")

            value.forEach { bean ->
                //去重
                if (!selectedPriceList.contains(bean)) {
                    selectedPriceList.add(bean)
                }
            }
        }

        selectedPriceList.forEach { bean ->
            val goodsBean = SelectedPriceDateEntity()

            //防止服务器不尊守约定返回为null类型
            goodsBean.date = if (bean.lineDate.isNullOrEmpty()) {
                ""
            } else {
                bean.lineDate
            }
            goodsBean.goodsNo = if (bean.storeNo.isNullOrEmpty()) {
                ""
            } else {
                bean.storeNo
            }
            //商品单价
            goodsBean.price = bean.sellPrice
            totalPrice += bean.sellPrice

            selectedPriceDateList.add(goodsBean)
        }
        payFee = totalPrice * num
        tvPrice.text = MoneyTool.formatFen(payFee)
    }

    //根据用户选择的班次时刻表 同步显示每站的时间表(stations中处理站点信息的时间点 站点之间需要累加实现总时间)
    private fun refreshBusTimeList() {
        var totalTime = 0
        stationsList.forEachIndexed { index, station ->
            for (i in 0..index) {
                if (i == index) {
                    totalTime += station.time
                    break
                }
            }
            station.timeAdd = TimeTool.formatTimeAdd(defaultLineTime, totalTime.toString())
        }

        //刷新之后需要 同步站点的时间点 记录当前选择的起点和终点的位置
        if (mStartPosition == DEFAULT_POS) {
            mStartPosition = 0
        }
        if (mEndPosition == DEFAULT_POS) {
            mEndPosition = stationsList.lastIndex
        }

        tvStartTimePlan.text =
            String.format(ResourcesUtil.getString(R.string.home_plan_time), stationsList[mStartPosition].timeAdd)
        tvEndTimePlan.text =
            String.format(ResourcesUtil.getString(R.string.home_plan_time), stationsList[mEndPosition].timeAdd)

    }

    //优化体验，用户选择起点和终点 从起点选择后开始选择
    private fun clearEndStation() {
        addressEndList.clear()

        for (k in mStartPosition + 1 until stationsList.size) {
            addressEndList.add(stationsList[k].name)
        }
    }

    private fun findIndexByName(name: String): Int {
        stationsList.forEachIndexed { index, station ->
            if (name == station.name) {
                return index
            }
        }
        return DEFAULT_POS
    }
}